/**
 * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License. 
 */
import { DateObject } from '../types/common';
import { DateFormatInfo, UseDateFormat } from './types';
import { NameOfMonths } from '../types/month';

export function useDateFormat(): UseDateFormat {

    function getDateValue(dateStr: string, dateFormat: string, delimeters: string[] | null): DateFormatInfo[] {
        const da: DateFormatInfo[] = [];

        if (delimeters) {
            let del: string = delimeters[0];
            if (delimeters[0] !== delimeters[1]) {
                del = delimeters[0] + delimeters[1];
                if (delimeters[2] && delimeters[1] !== delimeters[2]) {
                    del += delimeters[2];
                }
            }
            const re: any = new RegExp('[' + del + ']');
            const ds: Array<string> = dateStr.split(re);
            const df: Array<string> = dateFormat.split(re);
            for (let i = 0; i < df.length; i++) {
                if (df[i].indexOf('yyyy') !== -1) {
                    da[0] = { value: ds[i], format: df[i] };
                }
                if (df[i].indexOf('M') !== -1) {
                    da[1] = ds[i] === undefined ? { value: '1', format: df[i] } : { value: ds[i], format: df[i] };
                }
                if (df[i].indexOf('d') !== -1) {
                    da[2] = ds[i] === undefined ? { value: '1', format: df[i] } : { value: ds[i], format: df[i] };
                }
            }
        } else {
            const yearIndex = (dateFormat + '').indexOf('yyyy');
            const monthIndex = (dateFormat + '').indexOf('MM');
            const dayIndex = (dateFormat + '').indexOf('dd');
            if (yearIndex >= 0) {
                da[0] = { value: dateStr.substring(yearIndex, yearIndex + 4), format: dateFormat.substring(yearIndex, yearIndex + 4) };
            }
            if (monthIndex >= 0) {
                da[1] = { value: dateStr.substring(monthIndex, monthIndex + 2), format: dateFormat.substring(monthIndex, monthIndex + 2) };
            }
            if (dayIndex >= 0) {
                da[2] = { value: dateStr.substring(dayIndex, dayIndex + 2), format: dateFormat.substring(dayIndex, dayIndex + 2) };
            }
        }
        return da;
    }

    function preZero(val: number): string {
        return val < 10 ? '0' + Number(val) : String(val);
    }

    function remove(format: string, delStr: string): string {
        const re = format.match(/[^(DdMmYy)]{1,}/g);
        const index = format.indexOf(delStr);

        if (index < 0) {
            return format;
        }
        if (index === 0) {
            if (re) {
                return format.substring(3);
            }
            return format.substring(2);
        }
        if (index + 2 === format.length) {
            if (re) {
                return format.substring(0, format.length - 3);
            }
            return format.substring(0, format.length - 2);
        }
        if (re) {
            return format.substring(0, index) + format.substring(index + 3);
        }
        return format.substring(0, index) + format.substring(index + 2);
    }

    function formatDate(date: DateObject, dateFormat: string, nameOfMonths: NameOfMonths): string {
        if (!date.month && dateFormat.indexOf('MM') === -1) {
            dateFormat = remove(dateFormat, 'MM');
        }
        if (!date.day && dateFormat.indexOf('dd') === -1) {
            dateFormat = remove(dateFormat, 'dd');
        }
        let formatted: string = dateFormat.replace('yyyy', String(date.year));

        if (dateFormat.indexOf('M') === -1) {
            formatted = formatted.replace('MM', '01');
        } else {
            if (dateFormat.indexOf('MMM') !== -1) {
                formatted = formatted.replace('MMM', nameOfMonths[date.month || 1]);
            }
            if (dateFormat.indexOf('MM') !== -1) {
                formatted = formatted.replace('MM', preZero(date.month || 1));
            } else {
                formatted = formatted.replace('M', String(date.month || 1));
            }
        }

        if (dateFormat.indexOf('dd') === -1) {
            formatted = formatted.replace('dd', '01');
        } else if (dateFormat.indexOf('dd') !== -1) {
            formatted = formatted.replace('dd', preZero(date.day || 1));
        } else {
            formatted = formatted.replace('d', String(date.day || 1));
        }

        formatted = formatted.replace('MM', 'mm').replace('HH', preZero(date.hour || 0))
            .replace('mm', preZero(date.minute || 0))
            .replace('ss', preZero(date.second || 0));

        return formatted && formatted.length > 2 ? formatted : '';
    }

    return { getDateValue, formatDate, preZero, remove };
}
